package com.kuizii.auth.util;


import com.auth0.jwt.JWT;
import com.auth0.jwt.JWTVerifier;
import com.auth0.jwt.algorithms.Algorithm;
import com.auth0.jwt.exceptions.JWTDecodeException;
import com.auth0.jwt.exceptions.TokenExpiredException;
import com.auth0.jwt.interfaces.DecodedJWT;
import lombok.extern.slf4j.Slf4j;
import org.apache.shiro.authc.AuthenticationException;
import org.springframework.util.StringUtils;

import javax.servlet.ServletRequest;
import javax.servlet.http.HttpServletRequest;
import java.time.LocalDateTime;
import java.time.ZoneOffset;
import java.util.Date;


/**
 * @Author: nuanyang
 * @Date: 2019/7/24 0024 14:35
 */
@Slf4j
public class AuthUtils {

    private static final String secret = "text.your.secret.here";

    public static String getToken(ServletRequest request) {

        try {
            String authorization = ((HttpServletRequest) request).getHeader("Authorization");

            String jwtToken = authorization;

            if (StringUtils.isEmpty(authorization)) {
                //throw new Exception(String.format("解析authorization出错 Authorization 为空 "));
                return null;
            }
            log.info("解析authorization ==>" + authorization);

            if (authorization.startsWith("Bearer")) {
                jwtToken = StringUtils.split(authorization, " ")[1];
            }

            return jwtToken;
        } catch (Exception e) {
            log.error(e.toString());
            return null;
        }
    }

    public static boolean verify(String token) {
        try {

            JWTVerifier jwtVerifier = JWT.require(Algorithm.HMAC256(secret))
                    .build();

            DecodedJWT jwt = jwtVerifier.verify(token);

            return true;
        } catch (TokenExpiredException e) {
            throw new AuthenticationException("身份凭证已过期！");
        } catch (Exception e) {
            throw new AuthenticationException("身份凭证无效或已过期！");
        }
    }

    /**
     * 获得token中的信息无需secret解密也能获得
     *
     * @return token中包含的用户名
     */
    public static String getUsername(String token) {
        try {
            DecodedJWT jwt = JWT.decode(token);
            return jwt.getClaim("user_name").asString();
        } catch (JWTDecodeException e) {
            return null;
        }
    }

    public static String getUserId(String token) {
        try {
            DecodedJWT jwt = JWT.decode(token);
            return jwt.getClaim("user_id").asString();
        } catch (JWTDecodeException e) {
            return null;
        }
    }
    public static Integer getPlatform(String token) {
        try {
            DecodedJWT jwt = JWT.decode(token);
            return jwt.getClaim("platform").asInt();
        } catch (JWTDecodeException e) {
            return null;
        }
    }

    public static String createToken(String userName, String userId, int platform) {

        String sign = JWT.create()
                .withClaim("user_name", userName)
                .withClaim("user_id", userId)
                .withClaim("platform",   platform)
                .withExpiresAt(Date.from(LocalDateTime.now().plusHours(24).toInstant(ZoneOffset.ofHours(8))))
                .sign(Algorithm.HMAC256(secret));
        return sign;
    }
}
